<?php
class Torrent extends CActiveRecord {
	private $_dump = null;
	public $torrentfile;
	private $_err_msg = '';
//	public $uploader = null;

	public function getErrMsg() { return $this->_err_msg; }
	
	public static function model($className=__CLASS__)
	{
		return parent::model($className);
	}

	/**
	 * @return string the associated database table name
	 */
	public function tableName()
	{
		return 'torrents';
	}

	public function rules()
	{
		return array(
			array('name, description', 'required'),
			array('info_hash', 'unique', 'message' => 'This torrent already exists!'),
			array('torrentfile', 'file', 'types' => 'torrent', 'on' => 'upload')
		);
	}

	public function safeAttributes() {
		return array('name', 'description');
	}

	public function relations() {
		return array(
			'uploader'=>array(self::BELONGS_TO, 'User', 'uploader_id'),
			'peers' => array(self::HAS_MANY, 'Peer', 'torrent_id')
		);
		
	}

	public function checkDump()
	{
		$this->_dump = Benc::decode_file($this->torrentfile->getTempName(), $this->torrentfile->getSize());
		return $this->validate_dump();
	}

	public function validate_dump() {
		if ($this->_dump === null OR !is_array($this->_dump))
			return false;

//		list($ann, $info) = Benc::dict_check($this->_dump, 'announce(string):info');
		list($info) = Benc::dict_check($this->_dump, 'info');
		list($dname, $plen, $pieces) =
			Benc::dict_check($info, 'name(string):piece length(integer):pieces(string)');

		if (strlen($pieces) % 20 != 0)
			$this->_err_msg = 'invalid pieces';

		$filelist = array();
		$totallen = Benc::dict_get($info, 'length', 'integer');
		if (isset($totallen)) {
			$filelist[] = array($dname, $totallen);
			$type = 'single';
		}
		else {
			$flist = Benc::dict_get($info, 'files', 'list');
			if (!isset($flist))
				$this->_err_msg = 'missing both length and files';
			if (!count($flist))
				$this->_err_msg = 'no files';
			$totallen = 0;
			foreach ($flist as $fn) {
				list($ll, $ff) = Benc::dict_check($fn, 'length(integer):path(list)');
				$totallen += $ll;
				$ffa = array();
				foreach ($ff as $ffe) {
					if ($ffe['type'] != 'string')
						$this->_err_msg = 'filename error';
					$ffa[] = $ffe['value'];
				}
				if (!count($ffa))
					$this->_err_msg = 'filename error';
				$ffe = implode('/', $ffa);
				$filelist[] = array($ffe, $ll);
			}
			$type = 'multi';
		}

		$this->info_hash = sha1(Benc::encode($info));
		return true;
	}

	public function getDump() {
		return $this->_dump;
	}

}

?>
